#pragma once
#include "JeayeSDK.h"

class JEAYESDK_API JCriticalSection
{
public:
	JCriticalSection() {
		InitializeCriticalSection(&m_CritSec);
	};

	~JCriticalSection() {
		DeleteCriticalSection(&m_CritSec);
	};

	void Lock() {
		EnterCriticalSection(&m_CritSec);
	};

	void Unlock() {
		LeaveCriticalSection(&m_CritSec);
	};

protected:
	CRITICAL_SECTION    m_CritSec;
};

class JEAYESDK_API JSingleLock
{
public:
	JSingleLock(JCriticalSection * plock)
	{
		m_pLock = plock;
		m_pLock->Lock();
	};

	~JSingleLock() {
		m_pLock->Unlock();
	};

protected:
	JCriticalSection * m_pLock;
};


class JEAYESDK_API JEvent
{
public:
	JEvent(bool bManualReset = false)
	{
		m_hEvent = CreateEvent(NULL, bManualReset, false, NULL);
	};

	virtual ~JEvent()
	{
		CloseHandle(m_hEvent);
	};
public:
	BOOL Set(void)
	{
		BOOL    bRet = false;
		bRet = ::SetEvent(m_hEvent);
		return bRet;
	};

	bool Wait(unsigned long ulTimeout)
	{
		if (ulTimeout == 0)
			ulTimeout = 0xffffffff;

		bool    bRet = false;
		if (WAIT_OBJECT_0 == WaitForSingleObject(m_hEvent, ulTimeout))
			bRet = true;
		return bRet;
	};

	BOOL Reset(void)
	{
		BOOL    bRet = false;
		bRet = ::ResetEvent(m_hEvent);
		return bRet;
	};

protected:
	HANDLE  m_hEvent;

};

class JEAYESDK_API JSemaphore
{
public:
	JSemaphore::JSemaphore(UINT nCount)
	{
		m_semaphore = ::CreateSemaphore(NULL, (LONG)nCount, MAXLONG, NULL);
	}

	JSemaphore::~JSemaphore(void)
	{
		::CloseHandle(m_semaphore);
	}

	void JSemaphore::Lock(void)
	{
		::WaitForSingleObject(m_semaphore, INFINITE);
	}

	void JSemaphore::Unlock(void)
	{
		::ReleaseSemaphore(m_semaphore, 1, NULL);
	}

private:
	HANDLE          m_semaphore;
};